#include "scenetable.h"
#include "ui_scenetable.h"
#include "scenetable_global.h"
#include "scenemark.h"
#include <QBuffer>
#include <QDebug>
#include <QMouseEvent>
#include <typeinfo>
#include <QFile>
#include <QXmlStreamWriter>

SceneTable::SceneTable(QWidget *parent) :
    QWidget(parent),
    ui(new Ui::SceneTable)
{
    ui->setupUi(this);
    this->maxID=1;
    this->isConfig=false;
}

void SceneTable::setScenePicFile(QString file)
{
    this->image_file=file;
    pic_image.load(file);
    setScenePic(pic_image);
}



void SceneTable::setScenePic(QImage pic)
{
    //pic_image.load(picFile);
    setAutoFillBackground(true);   // 这个属性一定要设置
    QPalette pal(palette());
    pal.setBrush(QPalette::Window, QBrush(pic.scaled(size(), Qt::IgnoreAspectRatio,
                                                     Qt::SmoothTransformation)));
    setPalette(pal);
    //qDebug()<<size();
}

void SceneTable::setSceneMarkSize(int x, int y,int size)
{
    SceneMark *index;
    foreach (index, this->list_scene)
    {
        index->resize(x,y);
        index->setFontSize(size);
    }
}


void SceneTable::setConfig(bool isconfig)
{
    this->isConfig=isconfig;
}

QList<SceneMark *> SceneTable::getScenes()
{
    return this->list_scene;
}

QList<SceneMark> list;

QByteArray SceneTable::saveScenes()
{
    QByteArray tmp_array;
    QBuffer buffer(&tmp_array);
    QDataStream out(&buffer);
    SceneMark *index;
    list.clear();
    foreach (index, this->list_scene) {
        list<<*index;
    }
    buffer.open(QIODevice::ReadWrite);
    out<<list;
    buffer.close();
    return tmp_array;
}

void SceneTable::loadScenes(QString filename)
{
    QByteArray tmp;
    QXmlStreamReader reader;
    //ui->gridLayout_2->removeWidget(st);
    this->clearScenes();

    QFile file(filename);
    file.open(QFile::ReadOnly);
    reader.setDevice(&file);
    while(!reader.atEnd()) {
        if(reader.isStartElement()) {
            if(reader.name() == "SceneView") {
                this->image_file=reader.attributes().value("ScenePic").toString();
                while(!reader.atEnd())
                {
                    if(reader.name()=="SceneMarks")
                    {
                        tmp=QByteArray::fromHex(reader.readElementText().toLatin1());
                        reader.readNext();
                    }
                    reader.readNext();
                }
            }
            else reader.readNext();
        } else {
            reader.readNext();
        }
    }
    // 如果读取过程中出现错误，那么输出错误信息
    if (reader.hasError()) {
        //qDebug() << "error: " << reader.errorString();
    }
    file.close();

    this->setScenePicFile(this->image_file);
    this->loadScenes(tmp);


}

//void SceneTable::saveScenes(QString filename)
//{
//    QFile file(filename);
//    SceneMark *index;
//    list.clear();
//    QList<SceneMark> savelist;
//    foreach (index, this->list_scene) {
//        list<<*index;
//    }
//    file.open(QIODevice::WriteOnly);
//    QDataStream out(&file);
//    out << savelist;

//}


//void SceneTable::loadScenes(QString filename)
//{
//    int chid;
//    SceneMark index;
//    QFile file(filename);
//    qDeleteAll(list_scene);
//    list_scene.clear();
//    list.clear();
//    file.open(QIODevice::ReadOnly);
//    QDataStream in(&file);
//    in>>list;
//    foreach (index, list)
//    {
//        SceneMark *newLabel = new SceneMark(this);
//        (*newLabel)=index;
//        this->addScenesMark(newLabel);
//        newLabel->move(this->width()*index.RelativeX(),this->height()*index.RelativeY());
//        chid=newLabel->getChannelID();
//        newLabel->setChannelID(chid);
//        newLabel->setValue(chid);
//        if(chid>this->maxID)
//            maxIDChanged(chid+1);
//    }

//    file.close();
//}


void SceneTable::loadScenes(QByteArray &data)
{
    QByteArray tmp_array;
    int chid;
    SceneMark index;
    //qDebug()<<&tmp_array;
    tmp_array.append(data);
    qDeleteAll(list_scene);
    list_scene.clear();
    list.clear();
    QBuffer buffer(&tmp_array);
    buffer.open(QIODevice::ReadOnly);
    QDataStream in(&buffer);
    in>>list;
    foreach (index, list)
    {
        SceneMark *newLabel = new SceneMark(this);
        (*newLabel)=index;
        this->addScenesMark(newLabel);
        newLabel->move(this->width()*index.RelativeX(),this->height()*index.RelativeY());
        chid=newLabel->getChannelID();
        newLabel->setChannelID(chid);
        newLabel->setValue(chid);
        if(chid>=this->maxID)
            maxIDChanged(chid+1);
        connect(newLabel,SIGNAL(newIDChanged(int)),this,SLOT(maxIDadd(int)));
        newLabel->raise();
    }
    buffer.close();
}

void SceneTable::clearScenes()
{
    qDeleteAll(this->list_scene);
    this->list_scene.clear();
    list.clear();
}

void SceneTable::setConfig()
{
    this->isConfig=true;
}

SceneTable::~SceneTable()
{
    delete ui;
}

void SceneTable::addScenesMark(SceneMark *mark)
{
    list_scene.append(mark);
    mark->show();
    mark->setAttribute(Qt::WA_DeleteOnClose);
}

void SceneTable::maxIDChanged(int newid)
{
    if(this->maxID<newid)
    {
        maxID=newid;
        emit chvalue_changed(newid);
    }
}

void SceneTable::maxIDadd(int newid)
{
    if(newid>this->maxID)
    this->maxIDChanged(newid+1);
}

void SceneTable::resizeEvent(QResizeEvent *)
{
    //pic_image.load(this->image_file);
    SceneMark *index;
    this->setScenePic(this->pic_image);
    this->lastWidth=this->width();
    this->lastHight=this->height();
    foreach (index, this->list_scene)
    {
        //qDebug()<<"x:"<<this->width()<<"y:"<<this->height();
        index->move(this->width()*index->RelativeX(),this->height()*index->RelativeY());
        //qDebug()<<this->width()*index->RelativeX()<<this->height()*index->RelativeY();
    }
}

void SceneTable::dragEnterEvent(QDragEnterEvent *event)
{
    if(this->isConfig)
    {
        if (children().contains(event->source())) {
            event->setDropAction(Qt::MoveAction);
            event->accept();
        } else {
            event->acceptProposedAction();
        }
    }
    else
        QWidget::dragEnterEvent(event);
}


void SceneTable::dropEvent(QDropEvent *event)
{
    if(this->isConfig)
    {
        if (event->mimeData()->hasFormat("application/x-scenetable")) {
            const QMimeData *mime = event->mimeData();

            QByteArray itemData = mime->data("application/x-scenetable");
            QDataStream dataStream(&itemData, QIODevice::ReadOnly);

            QPoint offset;int channelid;bool isconfig=false;
            dataStream  >> offset>>channelid;

            SceneMark *newLabel = new SceneMark(this);
            this->addScenesMark(newLabel);
            newLabel->move(event->pos()-offset);
            connect(newLabel,SIGNAL(newIDChanged(int)),this,SLOT(maxIDadd(int)));
            if(channelid<=0)
            {
                newLabel->setChannelID(maxID);
                newLabel->setValue(maxID);
                maxIDChanged(maxID+1);
                event->acceptProposedAction();
            }
            else
            {
                newLabel->setChannelID(channelid);
                newLabel->setValue(channelid);
                if (event->source() == this) {
                    event->setDropAction(Qt::MoveAction);
                    event->accept();
                } else {
                    event->acceptProposedAction();
                }
            }
            newLabel->setConfig();
            newLabel->setRelativeX((float)newLabel->x()/this->width());
            newLabel->setRelativeY((float)newLabel->y()/this->height());
        }
    }
    else
        QWidget::dropEvent(event);
}

void SceneTable::mousePressEvent(QMouseEvent *event)
{
    if(isConfig)
    {
        SceneMark *child = static_cast<SceneMark*>(childAt(event->pos()));
        if (!child)
            return;

        while(child->objectName()!="SceneMark")
        {
            child=static_cast<SceneMark*>(child->parentWidget());
            if(child->objectName()=="SceneTable")
                return;
        }
        QPoint hotSpot = event->pos() - child->pos();

        QByteArray itemData;
        QDataStream dataStream(&itemData, QIODevice::WriteOnly);
        dataStream  << QPoint(hotSpot)<<child->getChannelID();

        QMimeData *mimeData = new QMimeData;
        mimeData->setData("application/x-scenetable", itemData);
        //mimeData->setText(child->labelText());

        QDrag *drag = new QDrag(this);

        QPixmap pixmap(child->size());
        child->render(&pixmap);

        drag->setMimeData(mimeData);
        drag->setPixmap(pixmap);
        drag->setHotSpot(hotSpot);

        child->hide();

        if (drag->exec(Qt::MoveAction | Qt::CopyAction, Qt::CopyAction) == Qt::MoveAction)
        {
            this->list_scene.removeOne(child);
            //this->list_scenes.removeOne(*child);
            child->close();
        }
        else
            child->show();
    }
    else
    {
        QWidget::mousePressEvent(event);
    }
}
